---------------------------------------------------------------------------------
  -- Design Name : Test Bench Package
  -- File Name   : TBPkg.vhd
  -- Function    : Defines constants and components used for test bench
  -- Authors     : Mirko Francuski  2006/0225
  --               Milos Mihajlovic 2006/0039
  -- School      : University of Belgrade
  --               School for Electrical Engineering
  --               Department for Computer Engineering and Information Theory
  -- Subject     : VLSI Computer Systems
---------------------------------------------------------------------------------

library ieee;

use ieee.std_logic_1164.all;
use std.textio.all;

package TBPkg is

  -- constant definitions
  constant CLOCK_PERIOD       : time := 100 ps;
  constant CLOCK_HALF_PERIOD  : time := CLOCK_PERIOD / 2;
  constant DELAY              : time := CLOCK_PERIOD / 4;
  
  constant INT_MAX : integer := 2147483647;
  constant INT_MIN : integer := -2147483647;
   
  constant TESTPUBLIC         : string := "public-test";
  constant TESTBRANCH         : string := "branch-test";
  constant TESTHAZARDS        : string := "hazards-test";
  constant TESTJSR            : string := "jsr-test";
  constant TESTINST           : string := "inst-test";  
  constant TEST04             : string := "public-test";
  
  constant NBSP : CHARACTER      := CHARACTER'val(160);  -- space character
  
  -- converts a std_logic_vector into a hex string.
  function hstr(slv: std_logic_vector) return string;
  
  -- converts a character into std_logic
  function to_std_logic(c: character) return std_logic; 
    
  -- converts a string into std_logic_vector
  function to_std_logic_vector(s: string) return std_logic_vector;
  
  component Clock is
    port (
      clk : out std_logic
    );
  end component;
  
end;

package body TBPkg is

  function hstr(slv: std_logic_vector) return string is
    variable hexlen: integer;
    variable longslv : std_logic_vector(67 downto 0) := (others => '0');
    variable hex : string(1 to 16);
    variable fourbit : std_logic_vector(3 downto 0);
  begin
    hexlen := (slv'left+1)/4;
    if (slv'left+1) mod 4 /= 0 then
    hexlen := hexlen + 1;
    end if;
    longslv(slv'left downto 0) := slv;
    for i in (hexlen - 1) downto 0 loop
      fourbit := longslv(((i * 4) + 3) downto (i * 4));
      case fourbit is
        when "0000" => hex(hexlen - I) := '0';
        when "0001" => hex(hexlen - I) := '1';
        when "0010" => hex(hexlen - I) := '2';
        when "0011" => hex(hexlen - I) := '3';
        when "0100" => hex(hexlen - I) := '4';
        when "0101" => hex(hexlen - I) := '5';
        when "0110" => hex(hexlen - I) := '6';
        when "0111" => hex(hexlen - I) := '7';
        when "1000" => hex(hexlen - I) := '8';
        when "1001" => hex(hexlen - I) := '9';
        when "1010" => hex(hexlen - I) := 'A';
        when "1011" => hex(hexlen - I) := 'B';
        when "1100" => hex(hexlen - I) := 'C';
        when "1101" => hex(hexlen - I) := 'D';
        when "1110" => hex(hexlen - I) := 'E';
        when "1111" => hex(hexlen - I) := 'F';
        when "ZZZZ" => hex(hexlen - I) := 'z';
        when "UUUU" => hex(hexlen - I) := 'u';
        when "XXXX" => hex(hexlen - I) := 'x';
        when others => hex(hexlen - I) := '?';
      end case;
    end loop;
    return hex(1 to hexlen);
  end hstr;
  
  -- converts a character into a std_logic
  function to_std_logic(c: character) return std_logic is 
    variable sl: std_logic;
    begin
      case c is
        when 'U' => 
           sl := 'U'; 
        when 'X' =>
           sl := 'X';
        when '0' => 
           sl := '0';
        when '1' => 
           sl := '1';
        when 'Z' => 
           sl := 'Z';
        when 'W' => 
           sl := 'W';
        when 'L' => 
           sl := 'L';
        when 'H' => 
           sl := 'H';
        when '-' => 
           sl := '-';
        when others =>
           sl := 'X'; 
    end case;
    return sl;
  end to_std_logic;
  
  -- converts a string into std_logic_vector
  function to_std_logic_vector(s: string) return std_logic_vector is 
    variable slv: std_logic_vector(s'high-s'low downto 0);
    variable k: integer;
  begin
    k := s'high-s'low;
    for i in s'range loop
       slv(k) := to_std_logic(s(i));
       k      := k - 1;
    end loop;
    return slv;
  end to_std_logic_vector;
  
end TBPkg;